linux 0.11下有一個目錄boot,
裏有3個組語檔。
bootsect.s
head.s
setup.s
我們來搞錄一些還沒有feeling的指令
bootsect.s,
260行,
mov cx,#256
sub si,si
sub di,di
rep
movw
.....................
load_setup:
mov dx,#0x0000 ! drive 0, head 0
mov cx,#0x0002 ! sector 2, track 0
mov bx,#0x0200 ! address = 512, in INITSEG
mov ax,#0x0200+SETUPLEN ! service 2, nr of sectors
int 0x13 ! read it
............................................
mov ah,#0x03 ! read cursor pos
xor bh,bh
int 0x10
.............................
read_it:
mov ax,es
test ax,#0x0fff
die: jne die ! es must be at 64kB boundary
xor bx,bx ! bx is starting address within segment
.......................................
sub ax,sread
mov cx,ax
shl cx,#9
....................
inc track
...................
/*
* This procedure turns off the floppy drive motor, so
* that we enter the kernel in a known state, and
* don't have to worry about it later.
*/
kill_motor:
push dx
mov dx,#0x3f2
mov al,#0
outb
pop dx
ret
movw,xor,outb,ret,inc,shl,test這些指令還沒練習過。
--------------------------------
head.s,238行
/*
* setup_idt
*
* sets up a idt with 256 entries pointing to
* ignore_int, interrupt gates. It then loads
* idt. Everything that wants to install itself
* in the idt-table may do so themselves. Interrupts
* are enabled elsewhere, when we can be relatively
* sure everything is ok. This routine will be over-
* written by the page tables.
*/
setup_idt:
lea ignore_int,%edx
movl $0x00080000,%eax
movw %dx,%ax /* selector = 0x0008 = cs */
movw $0x8E00,%dx /* interrupt gate - dpl=0, present */
lea _idt,%edi
mov $256,%ecx
rp_sidt:
movl %eax,(%edi)
movl %edx,4(%edi)
addl $8,%edi
dec %ecx
jne rp_sidt
lidt idt_descr
ret
lea,movl,dec,lidt這是一個以設定為主的組語檔
-----------------------------
setup.s
一開始一大堆的中斷,
! ok, the read went well so we get current cursor position and save it for ! posterity.
mov ax,#INITSEG ! this is done in bootsect already, but...
mov ds,ax
mov ah,#0x03 ! read cursor pos
xor bh,bh
int 0x10 ! save it in known place, con_init fetches
mov [0],dx ! it from 0x90000.
! Get memory size (extended mem, kB)
mov ah,#0x88
int 0x15
mov [2],ax
! Get video-card data:
mov ah,#0x0f
int 0x10
mov [4],bx ! bh = display page
mov [6],ax ! al = video mode, ah = window width
! check for EGA/VGA and some config parameters
mov ah,#0x12
mov bl,#0x10
int 0x10
mov [8],ax
mov [10],bx
mov [12],cx
! Get hd0 data
mov ax,#0x0000
mov ds,ax
lds si,[4*0x41]
mov ax,#INITSEG
mov es,ax
mov di,#0x0080
mov cx,#0x10
rep
movsb
! Get hd1 data
mov ax,#0x0000
mov ds,ax
lds si,[4*0x46]
mov ax,#INITSEG
mov es,ax
mov di,#0x0090
mov cx,#0x10
rep
movsb
...................................................
! well, that went ok, I hope. Now we have to reprogram the interrupts :-( ! we put them right after the intel-reserved hardware interrupts, at ! int 0x20-0x2F. There they won't mess up anything. Sadly IBM really ! messed this up with the original PC, and they haven't been able to ! rectify it afterwards. Thus the bios puts interrupts at 0x08-0x0f, ! which is used for the internal hardware interrupts as well. We just ! have to reprogram the 8259's, and it isn't fun.
mov al,#0x11 ! initialization sequence
out #0x20,al ! send it to 8259A-1
.word 0x00eb,0x00eb ! jmp $+2, jmp $+2
out #0xA0,al ! and to 8259A-2
.word 0x00eb,0x00eb
mov al,#0x20 ! start of hardware int's (0x20)
out #0x21,al
.word 0x00eb,0x00eb
mov al,#0x28 ! start of hardware int's 2 (0x28)
out #0xA1,al
.word 0x00eb,0x00eb
mov al,#0x04 ! 8259-1 is master
out #0x21,al
.word 0x00eb,0x00eb
mov al,#0x02 ! 8259-2 is slave
out #0xA1,al
.word 0x00eb,0x00eb
mov al,#0x01 ! 8086 mode for both
out #0x21,al
.word 0x00eb,0x00eb
out #0xA1,al
.word 0x00eb,0x00eb
mov al,#0xFF ! mask off all interrupts for now
out #0x21,al
.word 0x00eb,0x00eb
out #0xA1,al
lds si,[4*0x41],out #0xA1,al
目前還不理解的指令,
**小結:**期中來審視一下目標,
要多了解一些組語設定設備的指令,如軟碟機,VGA,所謂中斷的用法。
輸出out比較不理解其意思,在隨後的練習中補強。
以最近一本徹底研究Linux Kernel設計的藝術
一書中,第1章 從開機接上電源到執行main函數之前的過程。
1.1啟動bios, 準備真實模式下的中斷向量表和中斷服務程式
1.2載入作業系統核心程式並為保護模式做準備
1.2.1 載入第一部分程式-開機程式(bootsect)
1.2.2 載入第一部分程式-setup
1.2.3 載入第三部分程式-system模組。
1.3開始向32位元模式轉變,為main函數的呼叫做準備
-------------------------------
1.2的三個小節,並不是對應到3個組語檔。
而是1.2.1 ,1.2.2,對應到3個組語檔。
├── boot
│ ├── bootsect.s
│ ├── head.s
│ └── setup.s
14 directories, 100 files
雖說麻雀雖小,五臟俱全,linux0.11版時,還沒有聯上網路(實作tcp/ip)的功能。
以現在wifi無線上網那麼普遍,很難想像不能上網的OS有什麼實際用途,
那時候的網際網路,大概就是BBS,或是郵件論壇,
大家就用得很高興了,
linux就這樣一步一步,慢慢的壯大起來。
同期的OS,1991年,視窗系統都要出來了。
了解了,所以現在看的是原始檔,而不是反組譯kernel....
....想說為何開機時會去執行組語檔.......
祝Tim大週末愉快啦~~